.text

.global _start

_start:
    # close whatch dog
    ldr r0, =0x53000000
    ldr r1, = 0
    str r1,[r0]
    
    #设置MPLL,FCLK : HCLK : MCLK = 400m : 100m : 50m#
    #设置LOCKTIME(0x4000000) = 0xFFFFFFFF
    ldr r0, =0x4c000000
    ldr r1, =0xFFFFFFFF	
    str r1,[r0]
    
    #设置分频器CLKDIVN(0x4c000014) = 0x5
    ldr r0, =0x4c000014
    ldr r1, =0x5
    str r1, [r0]
    
    #设置cpu工作于异步模式,不然他会和hclk一样.
    mrc p15,0,r0,c1,c0,0
    orr r0,r0,#0xc0000000
    mcr p15,0,r0,c1,c0,0

    #设置MPLL(0x4c000004) = 92<<12 | 1<<4 | 1<<0
    ldr r0, =0x4c000004
    ldr r1, =(92<<12)|(1<<4)|(1<<0)
    str r1, [r0]



    # set stack
    #boot by nor or nand 
    #写0到0地址,再读出来
    #如果得到0,表示0地址上的内容被修改了,
    #它对应ram,这就是nand的启动.
    #否则就是nor启动
    mov r1,#0
    ldr r0,[r1] /* 读出原来的值备份一下*/
    str r1,[r1] /* 0>[0]*/
    ldr r2,[r1] /* p r2=[0]*/
    cmp r1,r2   /*  r1==r2?nand:nor*/
    ldr sp, =0x40000000+4096 /*  先假设nor启动*/
    moveq sp, #4096 /*  如果cmp成立则运行这句*/
    streq r0, [r1]  /*  恢复r0的值*/


    bl sdram_init   /* 初始化sdram,在重定位之前	*/

    #重定位text,rodata,data段的整个程序
    mov r1,#0
    ldr r2,=_start         /* 第一条指令运行地址 */
    ldr r3,=_bss_start

cpy:
    ldr r4,[r1]
    str r4,[r2]
    add r1,r1,#4
    add r2,r2,#4
    cmp r2,r3
    ble cpy

# 清除bss段
    ldr r1, =_bss_start
    ldr r2, =_end
    mov r3, #0

clean:
    strb r3,[r1]
    add r1,r1,#4
    cmp r1,r2
    ble clean

    //bl main  /* 使用bl命令相对跳转,程序仍然在NOR/sram执行 */
    ldr pc, =main /* 使用绝对命令跳转到sdram执行 */

halt:
    b halt
